Repository navigation
feat: build batch allowlist from descriptors, delete the hand list — Phase 1 step 4 - #909
Merged
Merged
Conversation
Contributor
Size Report
Startup median (7 runs, lower is better):
Top changed chunks:
|
This was referenced Jun 27, 2026
thymikee
force-pushed
the
feat/command-descriptor-capability-flip
branch
from
June 27, 2026 16:24
0203f17 to
1809b5a
Compare
thymikee
force-pushed
the
feat/command-descriptor-batch-flip
branch
from
June 27, 2026 16:25
7eecb1d to
9cffb43
Compare
thymikee
added a commit
that referenced
this pull request
Jun 27, 2026
…lify #909) — Phase 1 step 7 The command-descriptor registry is now `as const` (#910), so each entry keeps its literal `name` and literal `batchable`. Derive StructuredBatchCommandName from it via `Extract<…, { batchable: true }>['name']` instead of the 43-member hand-authored union from #909, and delete the now-tautological exhaustive Record membership assertion in parity.test.ts (type and value now derive from the same `batchable: true` entries). Strictly behaviorless: the derived union is the identical 43-member set (confirmed bidirectionally assignable to the old hand union, member count unchanged), the runtime allowlist value is unchanged, and the public BatchCommandName re-export is structurally identical (consumer switches on specific batch command names still typecheck).
thymikee
force-pushed
the
feat/command-descriptor-capability-flip
branch
from
June 27, 2026 18:06
1809b5a to
65d8816
Compare
thymikee
force-pushed
the
feat/command-descriptor-batch-flip
branch
from
June 27, 2026 18:07
9cffb43 to
7479e03
Compare
thymikee
added a commit
that referenced
this pull request
Jun 27, 2026
…lify #909) — Phase 1 step 7 The command-descriptor registry is now `as const` (#910), so each entry keeps its literal `name` and literal `batchable`. Derive StructuredBatchCommandName from it via `Extract<…, { batchable: true }>['name']` instead of the 43-member hand-authored union from #909, and delete the now-tautological exhaustive Record membership assertion in parity.test.ts (type and value now derive from the same `batchable: true` entries). Strictly behaviorless: the derived union is the identical 43-member set (confirmed bidirectionally assignable to the old hand union, member count unchanged), the runtime allowlist value is unchanged, and the public BatchCommandName re-export is structurally identical (consumer switches on specific batch command names still typecheck).
thymikee
force-pushed
the
feat/command-descriptor-batch-flip
branch
from
June 27, 2026 18:22
7479e03 to
6f5f872
Compare
thymikee
added a commit
that referenced
this pull request
Jun 27, 2026
…lify #909) — Phase 1 step 7 The command-descriptor registry is now `as const` (#910), so each entry keeps its literal `name` and literal `batchable`. Derive StructuredBatchCommandName from it via `Extract<…, { batchable: true }>['name']` instead of the 43-member hand-authored union from #909, and delete the now-tautological exhaustive Record membership assertion in parity.test.ts (type and value now derive from the same `batchable: true` entries). Strictly behaviorless: the derived union is the identical 43-member set (confirmed bidirectionally assignable to the old hand union, member count unchanged), the runtime allowlist value is unchanged, and the public BatchCommandName re-export is structurally identical (consumer switches on specific batch command names still typecheck).
Contributor
|
thymikee
added a commit
that referenced
this pull request
Jun 27, 2026
…lify #909) — Phase 1 step 7 The command-descriptor registry is now `as const` (#910), so each entry keeps its literal `name` and literal `batchable`. Derive StructuredBatchCommandName from it via `Extract<…, { batchable: true }>['name']` instead of the 43-member hand-authored union from #909, and delete the now-tautological exhaustive Record membership assertion in parity.test.ts (type and value now derive from the same `batchable: true` entries). Strictly behaviorless: the derived union is the identical 43-member set (confirmed bidirectionally assignable to the old hand union, member count unchanged), the runtime allowlist value is unchanged, and the public BatchCommandName re-export is structurally identical (consumer switches on specific batch command names still typecheck).
thymikee
added a commit
that referenced
this pull request
Jun 27, 2026
…lify #909) — Phase 1 step 7 The command-descriptor registry is now `as const` (#910), so each entry keeps its literal `name` and literal `batchable`. Derive StructuredBatchCommandName from it via `Extract<…, { batchable: true }>['name']` instead of the 43-member hand-authored union from #909, and delete the now-tautological exhaustive Record membership assertion in parity.test.ts (type and value now derive from the same `batchable: true` entries). Strictly behaviorless: the derived union is the identical 43-member set (confirmed bidirectionally assignable to the old hand union, member count unchanged), the runtime allowlist value is unchanged, and the public BatchCommandName re-export is structurally identical (consumer switches on specific batch command names still typecheck).
thymikee
added a commit
that referenced
this pull request
Jun 27, 2026
…lify #909) — Phase 1 step 7 (#912) The command-descriptor registry is now `as const` (#910), so each entry keeps its literal `name` and literal `batchable`. Derive StructuredBatchCommandName from it via `Extract<…, { batchable: true }>['name']` instead of the 43-member hand-authored union from #909, and delete the now-tautological exhaustive Record membership assertion in parity.test.ts (type and value now derive from the same `batchable: true` entries). Strictly behaviorless: the derived union is the identical 43-member set (confirmed bidirectionally assignable to the old hand union, member count unchanged), the runtime allowlist value is unchanged, and the public BatchCommandName re-export is structurally identical (consumer switches on specific batch command names still typecheck).
This was referenced Sep 23, 2026
thymikee
added a commit
that referenced
this pull request
Sep 23, 2026
…ntees (#2779) `commandDescriptors` claimed to be "proven byte-equal to the live hand tables by `__tests__/parity.test.ts`". Neither operand survives the ADR 0008 migration. The test is now `src/__tests__/command-descriptor-parity.test.ts` (moved by 2ec4e91 #2348); the tables it compared were deleted by the PRs that inverted them (47abc8c #907 daemon routes, 96bc7b1 #908 capability matrix, retired by ea1d6b8 #2089, 607883d #909 batch allowlist, 8ef4e73 #1137 MCP exposure); and TIMEOUT_POLICY_BY_COMMAND, DEVICE_CLAIM_POLICY_BY_COMMAND and COMMAND_DESCRIPTOR_BY_NAME are folds over this array, so byte-equality has no second operand. Record the invariant that does hold and name the check that carries each part, so a future split of this file preserves them. Established by mutation, not by reading: duplicating a descriptor fails owner-files.test.ts, command-descriptor-parity.test.ts and device-claim-policy.test.ts, while renaming one lands on the literal pins (targetIdentityVerification, the timeout and device-claim deviating sets). No new completeness test was owed here, and the compile-time totality guard already covers required traits. Same repair for the `frameworkTier` and `targetIdentityVerification` "the parity test" pointers, the two `@internal Introspection helper used by parity tests` docblocks (whose real consumers are command-descriptor-parity.test.ts and command-surface-metadata.test.ts), the "additive single source" banner that still listed the retired capability facet, and the CommandDescriptor intro, which described the deleted tables as "today" and cited `app-switcher` as unrouted after ADR 0014 gave it a daemon facet.
thymikee
added a commit
that referenced
this pull request
Sep 23, 2026
…ecord the descriptor-root block (#2808) * docs(adr): retire the parity-gate claim, state press-shape refusal, record the descriptor-root block ADR 0008 still promises a class of check that no longer exists. The parity test its migration rule required lost its second operand as each hand table was inverted out (#907, #908, #909, #1084, #1137); the retirement is recorded in Status and the present-tense claims are corrected, while the migration rule itself is left intact because it was followed. ADR 0019 gains the rule that a shape of an operation is not an operation and gets no fact cell, which is what a per-shape refusal on the owning leaf mechanic rests on. ADR 0027 records, without deciding, the conflict that makes the descriptor root unshippably splitable: ADR 0008's synchronous hub and the ADR-0019 eager-closure module-count budget have no shared approval path. Measured: any decomposition of the root, even the smallest, grows eleven entry surfaces. * docs(adr): propose one runtime source for the capability-family cell vocabulary Adding an operation family edits the cell key twice in one file: once as a property of UnavailablePlatformRuntimeFacts and again as a value in UNAVAILABLE_CELLS, which cannot be derived from the type. satisfies makes drift a compile error, so this is a maintenance tax rather than a soundness hole -- but it is why a file with fan-in 6 churned 9 times in 200 commits, and why one capability still fans out across eight packages. Proposes the inversion the repo already proved on the binding axis (INTERACTOR_OPERATIONS) for the facts axis, and states what it deliberately does not grant: no default-deny baseline, because ADR 0019 requires exhaustive per-shape facts and forbids cross-family defaults in a platform package. Gated on a measurement and on eager-closure neutrality, with withdrawal as an acceptable outcome. * docs(adr): point ADR 0027 at the pushed, recoverable descriptor split
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
Phase 1 step 4 of the command-descriptor migration (ADR-0008). Builds the structured-batch allowlist (
STRUCTURED_BATCH_COMMAND_NAMESinsrc/batch-policy.ts) from the command-descriptor registry'sbatchableflag viaderiveStructuredBatchCommandNames(commandDescriptors), and deletes the hand-authoredas constlist. The registry is now the single runtime source of truth for which commands are batchable.Behaviorless: #906 already proved derived membership equals the hand list (43 names, both sides). This slice flips the runtime value to the derived one; the parity test now guards the invariant instead of being a tautology.
How the
StructuredBatchCommandNametype was handledStructuredBatchCommandNameis a narrow union consumed beyond batch-policy:readStructuredBatchCommandNamereturns it,commands/batch/projection.tshasSTRUCTURED_BATCH_COMMAND_NAMES satisfies readonly DaemonCommandName[]and derivesBatchCommandName = (typeof batchCommandNames)[number], which is re-exported publicly viacommand-surface.ts.The registry types each
nameasstring, so deriving the value yieldsstring[]. Re-deriving the type from that value would widen the union tostring, break thesatisfiesguard, and widen the publicBatchCommandName. So the type is kept hand-authored as an explicit union of(typeof PUBLIC_COMMANDS)[...]members; only the runtime VALUE is derived (cast back to the narrow union). The parity test asserts the derived value's membership equals the kept union via an exhaustiveRecord<StructuredBatchCommandName, true>(compiler-enforced over the union) deep-equaled to the derived set — proving the type did not drift from the runtime value in either direction.tsc --noEmitpasses (exit 0), confirming no consumer type widened.Order check
The derived order follows the daemon table, not the old hand-list order. Confirmed no consumer is order-sensitive: the batch-policy consumer dedupes into a
Set;projection.ts:18usessatisfies(order-independent);metadata.tsfeeds the names into a JSON Schemaenum, but no snapshot/test asserts that enum's order (verified across.snapfiles and the mcp router / command-tools / command-surface-metadata suites). Cosmetic only — behaviorless.Tests
Updated the batch parity test (was a tautology after the flip) to an invariant: allowlist is built from the descriptors, no duplicates, membership equals the kept union, every batchable name is a public command, and control-plane commands (
batch,replay,prepare,pinch,viewport,pan,fling,rotate-gesture,transform-gesture) stay out. Kept the daemon-routing parity invariants untouched.Verification
tsc -p tsconfig.json --noEmit— exit 0oxfmt --write+oxlint --deny-warningson changed files — cleanvitest runbatch + core/command-descriptor + mcp router/command-tools + command-surface-metadata + core — all passStacked on #908 → #907 → #906.